package com.rao.mongodb.explorer.service.impl;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.rao.mongodb.explorer.common.config.ExplorerConfig;
import com.rao.mongodb.explorer.common.constants.ExplorerConstants;
import com.rao.mongodb.explorer.common.constants.SystemConstant;
import com.rao.mongodb.explorer.dao.DepotRepository;
import com.rao.mongodb.explorer.dao.ShortUrlRepository;
import com.rao.mongodb.explorer.dao.UFileRepository;
import com.rao.mongodb.explorer.entity.OFile;
import com.rao.mongodb.explorer.entity.ShortUrl;
import com.rao.mongodb.explorer.entity.UFile;
import com.rao.mongodb.explorer.service.IUFileService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.core.common.ResultMsg;
import javax.core.common.encrypt.DESStaticKey;
import javax.core.common.utils.FileUtils;
import javax.core.common.utils.ShortUrlUtils;
import javax.core.common.utils.StringUtils;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Optional;

/**
 * 文件操作实现
 *
 * @author raos
 * @emil 991207823@qq.com
 * @date 2021/8/31 22:16
 */
@Service
public class UFileService implements IUFileService {

    private static final String KEY = "TFmrluhJJC/=AiisvHkxutuyKGwzn3JhZfxX";

    @Autowired
    private ShortUrlRepository shortUrlRepo;

    @Autowired
    private DepotRepository depotRepo;

    @Autowired
    private UFileRepository uFileRepo;

    @Autowired
    private ExplorerConfig explorerConfig;

    @Override
    public ResultMsg<?> getTempPath() {
        ResultMsg<String> path = new ResultMsg<>(SystemConstant.RESULT_STATUS_SUCCESS);
        path.setData(explorerConfig.getTempRootDir());
        return path;
    }

    @Override
    public ResultMsg<?> list(String group, String uname, String path) {
        JSONArray result = new JSONArray();
        if (StringUtils.isEmpty(uname)) {
            uname = ExplorerConstants.ANONYMOUS;
        }
        List<UFile> list = uFileRepo.findAll();
        for (UFile uf : list) {
            if (uf.getFtype().equals(ExplorerConstants.FILE_TYPE_DIR)) {
                JSONObject fo = packageFile(uf);
                fo.put("type", "dir");
                result.add(fo);
            } else {
                String url = uf.getId();
                JSONObject fo = packageFile(uf);
                fo.put("url", url);
                fo.put("ext", uf.getExt());
                fo.put("size", uf.getFsize());
                fo.put("last", uf.getLastModified());
                fo.put("type", "file");
                result.add(fo);
            }
        }
        return new ResultMsg<Object>(SystemConstant.RESULT_STATUS_SUCCESS, "", result);
    }

    private JSONObject packageFile(UFile uf) {
        JSONObject fo = new JSONObject();
        fo.put("id", uf.getId());
        fo.put("pid", uf.getPid());
        fo.put("name", uf.getFname());
        fo.put("xpath", uf.getXpath());
        fo.put("fgroup", uf.getFgroup());
        return fo;
    }

    @Override
    public ResultMsg<?> download(String uname, String id) {
        Optional<UFile> uFile = uFileRepo.findById(id);
        String realPath = explorerConfig.getUsersRootDir()
                + uname.replaceAll("@|\\.", "/")
                + "/" + uFile.get().getFname();
        return new ResultMsg<Object>(SystemConstant.RESULT_STATUS_SUCCESS, "", new File(realPath));
    }

    @Override
    public ResultMsg<?> upload(String group, String uname, String path, Map<String, File> files) {
        try {
            JSONArray result = new JSONArray();
            List<ShortUrl> urls = new ArrayList<>();
            path = path.replaceAll("//", "/");
            for (String fileName : files.keySet()) {
                File src = files.get(fileName);
                UFile f = new UFile((path + "/" + fileName).replaceAll("/+", "/"));
                f.setCreateTime(System.currentTimeMillis());
                f.setLastModified(System.currentTimeMillis());
                f.setFsize(src.length());
                f.setFgroup(group);
                f.setOwner(uname);

                //保存到用户FTP目录
                String realPath = explorerConfig.getUsersRootDir()
                        + uname.replaceAll("@|\\.", "/") + "/" + path + "/";
                File udir = new File(realPath.replaceAll("//", "/"));
                if (!udir.exists()) {
                    udir.mkdirs();
                }
                FileUtils.copyFile(src.getAbsolutePath(), realPath + fileName);

                //保存到文件仓库
                OFile oFile = new OFile(src);
                oFile.setName(fileName);
                String objectId = depotRepo.putFile(oFile);

                f.setObjectId(objectId);
                uFileRepo.insert(f);

                //保存到数据库
                String url = DESStaticKey.encrypt(uname + "|" + objectId + "|" + path + "/" + fileName, KEY);
                String surl = ShortUrlUtils.getShortUrl(url);
                urls.add(new ShortUrl(surl, url));

                //组装返回值
                String ext = fileName.substring(fileName.lastIndexOf("."));
                JSONObject o = new JSONObject();
                o.put("originalName", path + fileName);
                o.put("name", fileName);
                o.put("url", surl);
                o.put("size", src.length());
                o.put("type", ext);
                o.put("last", src.lastModified());

                result.add(o);
                src.delete();
            }
            //生成短链接
            shortUrlRepo.saveAll(urls);

            return new ResultMsg<Object>(SystemConstant.RESULT_STATUS_SUCCESS, "", result);
        } catch (Exception e) {
            e.printStackTrace();
            return new ResultMsg<Object>(SystemConstant.RESULT_STATUS_FAILED, "上传失败");
        }
    }

}
